#!/usr/bin/perl -w
use strict; # always use strict, it's a good habit
use Parse::RecDescent; # see "perldoc Parse::RecDescent"


my $global_grammar = q{
  input: help | helpquit | quit | listlong | list | fileoption |
         <error>
  help: /help|h/i { ::usage(); 1; }
  helpquit: /-h/i { ::usage(); exit(0); }
  list: /list|l/i { system('/bin/ls'); 1; }
  listlong: /-l|listlong|ll/i { system('/bin/ls -l'); 1; }
  fileoption: /-f/i word { print "Configuration file is $item{word}\n"; 1; }
  quit: /quit|q/i { exit(0) }
  word: /\S+/
};

{ # this is a static scope!  do not remove!
 # $parse is only initialized once...
 my $parse = new Parse::RecDescent ($global_grammar);
 sub process_line
 {
  # get the input that was passed from above
  my $input = shift @_ || '';
  # return undef if the input is undef, or was not parsed correctly  
  $parse->input($input)
   or return undef; 
  # return 1 if everything went OK
  return 1;
 }
}
# first, process command-line arguments
if (@ARGV)			       
{
 process_line(join ' ', @ARGV);
}
                        do  {
 print "Type 'help' for help, or 'quit' to quit\n-> ";
 my $input = <STDIN>; # a variable to hold user input 
 print "You entered $input\n"; # let the user know what we got
 
 process_line($input);
} while (1); # only 'quit' or ^C can exit the loop
exit; # implicit exit here anyway
# print out the help and exit
sub usage
{
 print <<EOHIPPUS;
first.pl [-l] [-h] [-f FILENAME]
The -l switch lists the files in the current directory, using /bin/ls -l.
The -f switch selects a different configuration file.  The -h
switch prints this help.  Without the -l or -h arguments, will show
a command prompt.
Commands you can use at the prompt:
 list | l           : list the files in the current directory
 listlong | ll | -l : list the files in the current directory in long format
 help | h           : print out this help
 quit | q           : quit the program
 
EOHIPPUS
}